<?php

namespace App\Http\Controllers\CRM;

use App\Enums\OrderItemType;
use App\Enums\TradeStatus;
use App\Enums\UserType;
use App\Helper\ApiResponseHelper;
use App\Http\Controllers\Controller;
use App\Http\Resources\CRM\AssistantRankResource;
use App\Http\Resources\CRM\MemberRankResource;
use App\Http\Resources\CRM\UserRankResource;
use App\Models\AssistantRank;
use App\Models\MemberRank;
use App\Models\UserRank;
use App\Models\Order;
use App\Models\OrderItem;
use App\Models\Store;
use Illuminate\Http\Request;

class ServicesRankController extends Controller
{
    public function userRank(Store $store, Request $request)
    {
        $date = $request->input('date', now()->toDateString());
        [$start, $end] = $this->getDateMonthStartAndEnd($date);

        //获取当月的服务员排名 group by user_id 输出各字段的总和
        $ranks = UserRank::where('store_id', $store->id)
            ->whereBetween('count_date', [$start, $end])
            ->with('user.role')
            ->selectRaw('user_id, sum(total_money) as total_money, sum(total_table_money) as total_table_money, sum(total_goods_money) as total_goods_money, sum(total_assistant_money) as total_assistant_money, sum(total_services_point) as total_services_point, sum(total_point) as total_point')
            ->groupBy('user_id')
            ->orderBy('total_money', 'desc')
            ->get();

        return UserRankResource::collection($ranks);
    }

    public function getStoreUserCount(Store $store, Request $request)
    {
        $date = $request->input('date', now()->toDateString());
        [$start, $end] = $this->getDateMonthStartAndEnd($date);

        $orderQuery = Order::where('store_id', $store->id)
            ->where('status', TradeStatus::Payed)
            ->whereBetween('pay_at', [$start.' 00:00:00', $end.' 23:59:59']);
        $orderIds = $orderQuery->pluck('id');
        $itemQuery = OrderItem::whereIn('order_id', $orderIds);
        //总消费
        $totalMoney = $orderQuery->sum('money');
        //总台费
        $totalTableMoney = $itemQuery->where('type', OrderItemType::Table)
            ->sum('money');
        //总商品费
        $totalGoodsMoney = $itemQuery->where('type', OrderItemType::Goods)
            ->sum('money');
        //总陪打费
        $totalAssistantMoney = $itemQuery->where('type', OrderItemType::Assistant)
            ->sum('money');
        //总积分
        $totalServicesPoint = UserRank::where('store_id', $store->id)
            ->whereBetween('count_date', [$start, $end])
            ->sum('total_point');

        //计算多少天
        $days = (strtotime($end) - strtotime($start)) / 86400 + 1;
        //日均总消费
        $averageMoney = $totalMoney / $days;
        //日均总台费
        $averageTableMoney = $totalTableMoney / $days;
        //日均总商品费
        $averageGoodsMoney = $totalGoodsMoney / $days;
        //日均总陪打费
        $averageAssistantMoney = $totalAssistantMoney / $days;
        //日均总积分
        $averageServicesPoint = $totalServicesPoint / $days;

        return ApiResponseHelper::json([
            'count' => [
                'total_money' => round($totalMoney, 2),
                'total_table_money' => round($totalTableMoney, 2),
                'total_goods_money' => round($totalGoodsMoney, 2),
                'total_assistant_money' => round($totalAssistantMoney, 2),
                'total_services_point' => round($totalServicesPoint, 2),
            ],
            'average' => [
                'total_money' => round($averageMoney, 2),
                'total_table_money' => round($averageTableMoney, 2),
                'total_goods_money' => round($averageGoodsMoney, 2),
                'total_assistant_money' => round($averageAssistantMoney, 2),
                'total_services_point' => round($averageServicesPoint, 2),
            ]
        ]);
    }

    public function assistantRank(Store $store, Request $request)
    {
        $date = $request->input('date', now()->toDateString());
        [$start, $end] = $this->getDateMonthStartAndEnd($date);

        //获取当月的服务员排名 group by user_id 输出各字段的总和
        $ranks = AssistantRank::where('store_id', $store->id)
            ->whereBetween('count_date', [$start, $end])
            ->with('assistant.role')
            ->selectRaw('user_id, sum(total_minutes) as total_minutes, sum(total_assistant_minutes) as total_assistant_minutes, sum(total_inner_virtual_minutes) as total_inner_virtual_minutes, sum(total_outer_virtual_minutes) as total_outer_virtual_minutes, sum(total_assistant_count) as total_assistant_count, sum(total_point) as total_point')
            ->groupBy('user_id')
            ->orderBy('total_minutes', 'desc')
            ->get();

        return AssistantRankResource::collection($ranks);
    }

    public function getStoreAssistantCount(Store $store, Request $request)
    {
        $date = $request->input('date', now()->toDateString());
        [$start, $end] = $this->getDateMonthStartAndEnd($date);

        $orderQuery = Order::where('store_id', $store->id)
            ->where('status', TradeStatus::Payed)
            ->whereBetween('pay_at', [$start.' 00:00:00', $end.' 23:59:59']);
        $orderIds = $orderQuery->pluck('id');
        $orderItemsQuery = OrderItem::whereIn('order_id', $orderIds);
        $assistantOrderItemQuery = $orderItemsQuery->where('type', OrderItemType::Assistant);
        $assistantRankQuery = AssistantRank::where('store_id', $store->id)
            ->whereBetween('count_date', [$start, $end]);

        //总服务时长
        $totalMinutes = $assistantRankQuery->sum('total_minutes');
        //总金额
        $totalMoney = $assistantOrderItemQuery->sum('money');
        //总陪打时长
        $totalAssistantMinutes = $assistantRankQuery->sum('total_assistant_minutes');
        //总虚拟时长
        $totalVirtualMinutes = $assistantRankQuery->sum('total_inner_virtual_minutes') + $assistantRankQuery->sum('total_outer_virtual_minutes');
        //总陪打次数
        $totalAssistantCount = $assistantRankQuery->sum('total_assistant_count');

        //计算多少天
        $days = (strtotime($end) - strtotime($start)) / 86400 + 1;
        //日均总服务时长
        $averageMinutes = $totalMinutes / $days;
        //日均总金额
        $averageMoney = $totalMoney / $days;
        //日均总陪打时长
        $averageAssistantMinutes = $totalAssistantMinutes / $days;
        //日均总虚拟时长
        $averageVirtualMinutes = $totalVirtualMinutes / $days;
        //日均总陪打次数
        $averageAssistantCount = $totalAssistantCount / $days;

        return ApiResponseHelper::json([
            'count' => [
                'total_minutes' => $totalMinutes,
                'total_money' => $totalMoney,
                'total_assistant_minutes' => $totalAssistantMinutes,
                'total_virtual_minutes' => $totalVirtualMinutes,
                'total_assistant_count' => $totalAssistantCount,
            ],
            'average' => [
                'total_minutes' => $averageMinutes,
                'total_money' => $averageMoney,
                'total_assistant_minutes' => $averageAssistantMinutes,
                'total_virtual_minutes' => $averageVirtualMinutes,
                'total_assistant_count' => $averageAssistantCount,
            ]
        ]);
    }

    public function memberRank(Store $store, Request $request)
    {
        $date = $request->input('date', now()->toDateString());
        [$start, $end] = $this->getDateMonthStartAndEnd($date);

        $ranks = MemberRank::where('store_id', $store->id)
            ->whereBetween('count_date', [$start, $end])
            ->with('member')
            ->selectRaw('member_id, sum(total_money) as total, sum(total_assistant_minutes) as total_assistant_minutes, sum(total_assistant_count) as total_assistant_count, sum(total_assistant_project_count) as total_assistant_project_count, sum(total_assistant_project_minutes) as total_assistant_project_minutes, sum(total_point) as total_point')
            ->groupBy('member_id')
            ->orderBy('total', 'desc')
            ->get();

        return MemberRankResource::collection($ranks);
    }

    public function getStoreMemberCount(Store $store, Request $request)
    {
        $date = $request->input('date', now()->toDateString());
        [$start, $end] = $this->getDateMonthStartAndEnd($date);

        $orderQuery = Order::where('store_id', $store->id)
            ->where('status', TradeStatus::Payed)
            ->whereBetween('pay_at', [$start.' 00:00:00', $end.' 23:59:59'])
            ->whereNotNull('member_id');

        $orderItemQuery = OrderItem::whereIn('order_id', $orderQuery->pluck('id'));
        $assistantItemQuery = $orderItemQuery->where('type', OrderItemType::Assistant);
        $assistantItem = $assistantItemQuery->get();

        //总消费
        $totalMoney = $orderQuery->sum('money');
        //总助教时长
        $totalAssistantMinutes = 0;
        //总助教次数
        $totalAssistantCount = $assistantItemQuery->count();
        /**
         * @var OrderItem $item
         */
        foreach ($assistantItem as $item) {
            $totalAssistantMinutes += $item->getTotalMinutes($item->end_at);
        }
        //总点钟数
        $totalAssistantProjectCount = 0;    //TODO: 点钟？
        //总点钟时长
        $totalAssistantProjectMinutes = 0;

        //计算多少天
        $days = (strtotime($end) - strtotime($start)) / 86400 + 1;
        //日均总消费
        $averageMoney = $totalMoney / $days;
        //日均总助教时长
        $averageAssistantMinutes = $totalAssistantMinutes / $days;
        //日均总助教次数
        $averageAssistantCount = $totalAssistantCount / $days;
        //日均总点钟数
        $averageAssistantProjectCount = $totalAssistantProjectCount / $days;
        //日均总点钟时长
        $averageAssistantProjectMinutes = $totalAssistantProjectMinutes / $days;

        return ApiResponseHelper::json([
            'count' => [
                'total_money' => $totalMoney,
                'total_assistant_minutes' => $totalAssistantMinutes,
                'total_assistant_count' => $totalAssistantCount,
                'total_assistant_project_count' => $totalAssistantProjectCount,
                'total_assistant_project_minutes' => $totalAssistantProjectMinutes,
            ],
            'average' => [
                'total_money' => $averageMoney,
                'total_assistant_minutes' => $averageAssistantMinutes,
                'total_assistant_count' => $averageAssistantCount,
                'total_assistant_project_count' => $averageAssistantProjectCount,
                'total_assistant_project_minutes' => $averageAssistantProjectMinutes,
            ]
        ]);
    }

    private function getDateMonthStartAndEnd($date)
    {
        //获取当月第一天
        $start = date('Y-m-01', strtotime($date));
        //获取当月最后一天
        $end = date('Y-m-t', strtotime($date));
        return [$start, $end];
    }
}
